/*
 * ========================================================
 * Copyright(c) 2014 杭州偶尔科技-版权所有
 * ========================================================
 * 本软件由杭州偶尔科技所有, 未经书面许可, 任何单位和个人不得以
 * 任何形式复制代码的部分或全部, 并以任何形式传播。
 * 公司网址
 * 
 * 			http://www.kkkd.com/
 * 
 * ========================================================
 */
package com.simon.mengkou.future.impl;

import android.content.Context;

import com.ouertech.android.agm.lib.base.bean.BaseRequest;
import com.ouertech.android.agm.lib.base.constant.CstHttp;
import com.ouertech.android.agm.lib.base.future.core.AgnettyFuture;
import com.ouertech.android.agm.lib.base.future.core.AgnettyHandler;
import com.ouertech.android.agm.lib.base.future.core.AgnettyManager;
import com.ouertech.android.agm.lib.base.future.download.DownloadFuture;
import com.ouertech.android.agm.lib.base.future.http.HttpFuture;
import com.ouertech.android.agm.lib.base.future.local.LocalFuture;
import com.ouertech.android.agm.lib.base.future.upload.form.FormUploadFile;
import com.ouertech.android.agm.lib.base.future.upload.form.FormUploadFuture;
import com.ouertech.android.agm.lib.base.utils.UtilString;
import com.simon.mengkou.future.base.OuerFutureData;
import com.simon.mengkou.future.base.OuerFutureListener;
import com.simon.mengkou.future.base.OuerHeader;
import com.simon.mengkou.utils.UtilOuer;

import java.lang.reflect.Type;
import java.util.HashMap;
import java.util.Map;
import java.util.Objects;

/**
 * @author : Zhenshui.Xia
 * @date   :  2015-5-26
 * @desc   : 接口实现常用方法
 */
public abstract class AbsOuerFuture {
    //Ouerclient未初始化异常提示
    private static final String CALL_EXCEPTION_MSG  = "OuerFuture not init !!!";

    //统计请求头属性
    private static final String STAT_MFR 		= "_mfr";
    private static final String STAT_MODEL 		= "_model";
    private static final String STAT_SDK 		= "_sdk";
    private static final String STAT_CLIENT 	= "_client";
    private static final String STAT_DEVICE 	= "_device";
    private static final String STAT_VCODE 		= "_vcode";
    private static final String STAT_VNAME 		= "_vname";
    private static final String STAT_CH 		= "_ch";
    private static final String STAT_IMEI 		= "_imei";
    private static final String STAT_OSID 		= "_osid";
    private static final String STAT_MAC 		= "_mac";
    private static final String STAT_DID 		= "_did";
    private static final String STAT_SIZE 		= "_size";
    private static final String STAT_NET 		= "_net";
    private static final String STAT_APN 		= "_apn";
    private static final String STAT_IP 		= "_ip";

    //请求头属性map
    protected Map<String, String> mProperties;
    //上下文
    private Context mContext;


    public AbsOuerFuture(Context context, String project,
                            boolean debug, boolean cookie) {
        if(context == null
                || UtilString.isBlank(project)) {
            throw new RuntimeException("OuerFuture init() params error!!!");
        }

        mContext = context;
        //初始化任务管理器
        AgnettyManager manager = AgnettyManager.getInstance(context);
        manager.setProject(project);
        manager.setDebugEnable(debug);
        manager.setCookieEnable(cookie);

        //请求头添加统计数据
        OuerHeader stat = UtilOuer.getOuerHeader(context);
        mProperties = new HashMap<String, String>();
        mProperties.put(CstHttp.CONTENT_TYPE, CstHttp.APPLICATION_URLENCODED_FORM);
        mProperties.put(CstHttp.ACCEPT, CstHttp.APPLICATION_JSON);
        mProperties.put(CstHttp.ACCEPT_LANGUAGE, UtilOuer.getLocale());
        mProperties.put(STAT_MFR, 		stat.getManufacturer());
        mProperties.put(STAT_MODEL, 	stat.getModel());
        mProperties.put(STAT_SDK, 		String.valueOf(stat.getSdk()));
        mProperties.put(STAT_CLIENT, 	stat.getClient());
        mProperties.put(STAT_DEVICE, 	stat.getDevice());
        mProperties.put(STAT_VCODE, 	String.valueOf(stat.getVersionCode()));
        mProperties.put(STAT_VNAME, 	stat.getVersionName());
        mProperties.put(STAT_CH, 		stat.getAppChannel());
        mProperties.put(STAT_IMEI, 		stat.getImei());
        mProperties.put(STAT_OSID, 		stat.getOsId());
        mProperties.put(STAT_MAC, 		stat.getMac());
        mProperties.put(STAT_DID, 		stat.getDeviceId());
        mProperties.put(STAT_SIZE,      stat.getSize());
        mProperties.put(STAT_NET,       stat.getNetType());
        mProperties.put(STAT_APN,       stat.getApnType());
        mProperties.put(STAT_IP,        stat.getIpAddress());
    }


    /**
     * 清除cookie
     */
    public void clearCookie() {
        AgnettyManager.getInstance(mContext).clearCookie();
    }

    /**
     * 延时任务
     * @param delay
     * @param handler
     * @param listener
     * @return
     */
    public AgnettyFuture execLocalFuture(int delay,
                                         Class<? extends AgnettyHandler> handler,
                                         OuerFutureListener listener){
        //调用接口前未调用初始化方法init(context, project, debug, cookie)
        if(mContext == null) {
            throw new RuntimeException(CALL_EXCEPTION_MSG);
        }

        return new LocalFuture.Builder(mContext)
                .setHandler(handler)
                .setDelay(delay)
                .setListener(listener)
                .execute();
    }

    /**
     * 延时任务
     * @param delay
     * @param handler
     * @param listener
     * @return
     */
    public AgnettyFuture execLocalFuture(int delay,
                                         Object data,
                                         Class<? extends AgnettyHandler> handler,
                                         OuerFutureListener listener){
        //调用接口前未调用初始化方法init(context, project, debug, cookie)
        if(mContext == null) {
            throw new RuntimeException(CALL_EXCEPTION_MSG);
        }

        return new LocalFuture.Builder(mContext)
                .setHandler(handler)
                .setDelay(delay)
                .setData(data)
                .setListener(listener)
                .execute();
    }

    /**
     * 定时任务
     * @param handler
     * @param listener
     * @return
     */
    public AgnettyFuture execLocalScheduleFuture(int startTime, int intervalTime, int maxTime,
                                                 Class<? extends AgnettyHandler> handler,
                                                 OuerFutureListener listener){
        //调用接口前未调用初始化方法init(context, project, debug, cookie)
        if(mContext == null) {
            throw new RuntimeException(CALL_EXCEPTION_MSG);
        }

        return new LocalFuture.Builder(mContext)
                .setHandler(handler)
                .setSchedule(startTime, intervalTime, maxTime)
                .setListener(listener)
                .execute();
    }



    /**
     * 执行http get请求任务
     * @param url		接口地址
     * @param handler	业务逻辑处理器
     * @param tag       请求标签
     * @param req		请求数据
     * @param respType	响应数据类型
     * @param listener 请求响应监听器
     * @return
     */
    public AgnettyFuture execHttpGetFuture(String url,
                  Class<? extends AgnettyHandler> handler,
                  String tag,
                  BaseRequest req,
                  Type respType,
                  OuerFutureListener listener) {
        //调用接口前未调用初始化方法init(context, project, debug, cookie)
        if(mContext == null) {
            throw new RuntimeException(CALL_EXCEPTION_MSG);
        }

        return new HttpFuture.Builder(mContext, CstHttp.GET)
                .setUrl(url)
                .setTag(tag)
                .setHandler(handler)
                .setData(new OuerFutureData(req, respType))
                .setListener(listener)
                .setProperties(mProperties)
                .execute();
    }


    /**
     * 执行http get请求延时任务
     * @param url		接口地址
     * @param handler	业务逻辑处理器
     * @param tag       请求标签
     * @param req		请求数据
     * @param respType	响应数据类型
     * @param delay		延时时间（毫秒）
     * @param listener 请求响应监听器
     * @return
     */
    public AgnettyFuture execHttpGetDelayFuture(String url,
                   Class<? extends AgnettyHandler> handler,
                   String tag,
                   BaseRequest req,
                   Type respType,
                   int delay,
                   OuerFutureListener listener) {
        //调用接口前未调用初始化方法init(context, project, debug, cookie)
        if(mContext == null) {
            throw new RuntimeException(CALL_EXCEPTION_MSG);
        }

        return new HttpFuture.Builder(mContext, CstHttp.GET)
                .setUrl(url)
                .setTag(tag)
                .setHandler(handler)
                .setData(new OuerFutureData(req, respType))
                .setDelay(delay)
                .setListener(listener)
                .setProperties(mProperties)
                .execute();
    }


    /**
     * 执行http post请求任务
     * @param url		接口地址
     * @param handler	业务逻辑处理器
     * @param tag       请求标签
     * @param req		请求数据
     * @param respType	响应数据类型
     * @param listener 请求响应监听器
     * @return
     */
    public AgnettyFuture execHttpPostFuture(String url,
                   Class<? extends AgnettyHandler> handler,
                   String tag,
                   BaseRequest req,
                   Type respType,
                   OuerFutureListener listener) {
        //调用接口前未调用初始化方法init(context, project, debug, cookie)
        if(mContext == null) {
            throw new RuntimeException(CALL_EXCEPTION_MSG);
        }

        return new HttpFuture.Builder(mContext, CstHttp.POST)
                .setUrl(url)
                .setTag(tag)
                .setHandler(handler)
                .setData(new OuerFutureData(req, respType))
                .setListener(listener)
                .setProperties(mProperties)
                .execute();
    }


    /**
     * 执行http post请求延时任务
     * @param url		接口地址
     * @param handler	业务逻辑处理器
     * @param tag       请求标签
     * @param req		请求数据
     * @param respType	响应数据类型
     * @param delay		延时时间（毫秒）
     * @param listener 请求响应监听器
     * @return
     */
    public AgnettyFuture execHttpPostDelayFuture(String url,
                    Class<? extends AgnettyHandler> handler,
                    String tag,
                    BaseRequest req,
                    Type respType,
                    int delay,
                    OuerFutureListener listener) {
        //调用接口前未调用初始化方法init(context, project, debug, cookie)
        if(mContext == null) {
            throw new RuntimeException(CALL_EXCEPTION_MSG);
        }

        return new HttpFuture.Builder(mContext, CstHttp.POST)
                .setUrl(url)
                .setTag(tag)
                .setHandler(handler)
                .setData(new OuerFutureData(req, respType))
                .setDelay(delay)
                .setListener(listener)
                .setProperties(mProperties)
                .execute();
    }

    /**
     * 执行HTTP form upload任务
     * @param url
     * @param handler
     * @param tag       请求标签
     * @param req
     * @param listener
     * @param files
     * @return
     */
    protected AgnettyFuture execFormUploadFuture(String url,
                         Class<? extends AgnettyHandler> handler,
                         String tag,
                         BaseRequest req,
                         Type respType,
                         OuerFutureListener listener,
                         FormUploadFile... files) {
        //调用接口前未调用初始化方法init(context, project, debug, cookie)
        if(mContext == null) {
            throw new RuntimeException(CALL_EXCEPTION_MSG);
        }

        return new FormUploadFuture.Builder(mContext)
                .setUrl(url)
                .setTag(tag)
                .setHandler(handler)
                .setData(new OuerFutureData(req, respType))
                .setUploadFiles(files)
                .setListener(listener)
                .setProperties(mProperties)
                .execute();
    }


    //===============download future===============
    /**
     * 应用下载
     */
    public AgnettyFuture execDownloadFuture(String url, String filePath,
                                     OuerFutureListener listener) {
        return  new DownloadFuture.Builder(mContext)
                .setUrl(url)
                .setDownloadMode(DownloadFuture.REGET_MODE)
                .setPath(filePath)
                .setListener(listener)
                .execute();
    }


}
